import { computed, defineComponent, onMounted, onUnmounted, watchEffect } from "vue";
import type { ColumnProps, TableStore } from ".";
import Colgroup from "./Colgroup";
import Cell from "./Cell";

export interface SummaryProps {
    data: TableStore
    summaryMethod?: (columns: ColumnProps[], data: any[]) => any
    onResizeSummary: (width: number, height: number) => void
}

export default defineComponent({
    name: 'Summary',
    props: ['data', 'summaryMethod', 'onResizeSummary'],
    setup (props) {
        let summary: any;
        const summaryData = computed(() => {
            let row: any = {};
            if (props.summaryMethod) {
                row = props.summaryMethod(props.data.columns, props.data.data);
            } else {
                props.data.columns.forEach((col: ColumnProps, index: number) => {
                    const key = col.name!;
                    if (index === 0) {
                        row[key] = '合计';
                        return;
                    }
                    const values = props.data.data.map(item => Number(item[key]));
                    if (!values.every(value => isNaN(value))) {
                        const v = values.reduce((prev, curr) => {
                            const value = Number(curr);
                            if (!isNaN(value)) {
                                return prev + curr;
                            } else {
                                return prev;
                            }
                        }, 0);
                        row[key] = v;
                    } else {
                        row[key] = '';
                    }
                });
            }
            return row;
        });

        watchEffect(() => {
            if (summary) {
                summary.scrollLeft = props.data.headerLeft;
            }
        });

        const onEntryResize = (entry: ResizeObserverEntry) => {
            const el = entry.target;
            if (el.classList.contains("cm-table-summary")) {
                const rect = el.getBoundingClientRect();
                const tableH = el.children[0].getBoundingClientRect().height;

                props.onResizeSummary(rect.width, tableH);
                summary.style.height = tableH + 'px';
            } else {
            // setTimeout, header变化让body设置height后再计算是否有垂直滚动条
                setTimeout(() => {
                    const rect = el.getBoundingClientRect();
                    const parentRect = el.closest(".cm-table-body")!.getBoundingClientRect();

                    if (rect.height > parentRect.height) {
                        summary.style.overflowY = 'scroll';
                    } else {
                        summary.style.overflowY = '';
                    }
                });
            }
        };

        onMounted(() => {
            const ro = new ResizeObserver((entries) => {
                entries.forEach((entry) => onEntryResize(entry));
            });
            ro.observe(summary);
            const parent = summary.closest('.cm-table');
            const body = parent.querySelector('.cm-table-body-wrap');
            ro.observe(body);
            onUnmounted(() => {
                ro.unobserve(summary);
                ro.unobserve(body);
            });
        });

        return <div class="cm-table-summary" ref={summary}>
            <table>
                <Colgroup data={props.data}/>
                <thead style={{display: 'none'}}>
                    <tr>
                        {
                            props.data.columns.map((col: ColumnProps, index: number) => {
                                return <Cell column={col} type="th" placeholder colIndex={index} checkedAll={props.data.checkedAll}/>;
                            })
                        }
                    </tr>
                </thead>
                <tbody>
                    <tr>
                        {
                            props.data.columns.map((col: ColumnProps, index: number) => {
                                return <Cell type="td" summary data={summaryData.value} column={col} colIndex={index} index={index}
                                    showFixedLeft={props.data.showFixedLeft}
                                    showFixedRight={props.data.showFixedRight}/>;
                            })
                        }
                    </tr>
                </tbody>
            </table>
        </div>;
    }
});
